<template>
  数组的基类：<br>
  <el-button @click="change1" >修改状态</el-button>
  <el-button @click="reset" >重置</el-button>
  <el-button @click="setValue" >赋值</el-button>
  <br>
  <el-button @click="add1" >在开头添加</el-button>
  <el-button @click="add2" >在第三位添加</el-button>
  <el-button @click="del1" >删除开头</el-button>
  <el-button @click="del2" >从 1 开始 删掉 2 个</el-button>
  <el-button @click="del3" >删掉最后一个</el-button>
  <br>
  <el-button @click="swap" >交换 2 和 4 </el-button>

  <hr>
  初始值是数组：<br>
  nfState：{{nfState}}<br>
  nfStateRet：{{nfStateRet}}<br><br>
  初始值是函数：<br>
  nfState2：{{nfState2}}<br>
  nfStateRet2：{{nfStateRet2}}<br>

  
  <hr>
</template>

<script lang="ts">
  import { defineComponent, reactive, watch  } from 'vue'

  import {
    BaseArray
  } from '../../../lib/main'

  /**
   * 测试数组的基类
   * * 赋值，修改，重置
   * * 数组的各种操作
   * * 用数组定义、用函数定义
   */
  export default defineComponent({
    name: 'nf-state-base-array',
    props: {
   
    },
    setup(props, context) {
      // 数组，不支持 reset()
      const nfState = new BaseArray([
        {
          name: '初始值是数组1',
          age: 10
        },
        {
          name: '初始值是数组2',
          age: 10
        }
      ])

      // 函数，支持 reset()
      const nfState2 = new BaseArray(() => {
        return [
          {
            name: '初始值是函数1',
            age: 10
          },
          {
            name: '初始值是函数2',
            age: 10
          }
        ]
      })

      // 响应性
      const nfStateRet = reactive(nfState)
      const nfStateRet2 = reactive(nfState2)
      // 看看结构
      console.log('nfState', nfState)
      console.log('nfStateRet', nfStateRet)
      console.log('nfState2', nfState2)
      console.log('nfStateRet2', nfStateRet2)

      // 看遍历出来的key，只有数组下标
      for (const key in nfState) {
        console.log(key)
      }
      console.log('nfState —— keys:', Object.keys(nfState))
  
      // 修改
      const change1 = () => {
        /**/
        nfStateRet[0].name = '直接修改' + new Date().valueOf().toString()
      }

      // 重置
      const reset = () => {
        nfStateRet.$reset()
        nfStateRet2.$reset()
      }
      
      // 直接赋值
      const setValue = () => {
        nfStateRet.$state = [
          {
            name: new Date().valueOf().toString(),
            age: 10
          },
          {
            name: new Date().valueOf().toString(),
            age: 20
          }
        ]
        
        nfStateRet2.$state = [
          {
            name: new Date().valueOf().toString()
          }
        ]
      }

      // 监听，被改掉后，会失去监控
      watch(nfStateRet[0], (val1, val2) => {
        console.log('watch ：', val1, val2)
      })
      
      // 监听，被改掉后，依然有效，但是 reset 无效。
      watch(() => nfStateRet[0].name, (val1, val2) => {
        console.log('watch ：', val1, val2)
      })
      
      // 测试语法糖
      let i = 1
      // 首部添加
      const add1 = () => {
        nfStateRet2.$pushA({
          name: '第一个' + i++
        })
      }

      // 在第三位添加
      const add2 = () => {
        nfStateRet2.$pushAt(2, {
          name: '第三个' + i++
        })
      }

      // 删除第一个
      const del1 = () => {
        nfStateRet2.$deleteA()
      }

      // 从指定位置 i 开始的 n 个元素
      const del2 = () => {
        const re = nfStateRet2.$deleteAt(1,2)
        console.log('被减掉的：', re)
      }
      
      // 删除最后一个
      const del3 = () => {
        nfStateRet2.$deleteZ()
      }

      // 交换 2 和 4
      const swap = () => {
        nfStateRet2.$swap(2,4)
        console.log('交换后：', nfStateRet2)
      }

      return {
        nfState,
        nfState2,
        nfStateRet,
        nfStateRet2,
        // 扩展
        add1,
        add2,
        del1,
        del2,
        del3,
        swap,
        // 基础
        change1,
        reset,
        setValue
      }
    }
  })
</script>